﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using DotSpatial.Symbology;
using DotSpatial.Data;
using DotSpatial.Topology;
using DotSpatial.Controls;
using GisContour;
using System.ComponentModel;
using System.Windows.Forms;

using System.Drawing;


namespace HAGISV2
{
    [Serializable]
    public class IsolineLayer:SingleBaseLayer
    {
        public IsolineLayer(string id)
            : base(id)
        {
            _featureType = FeatureType.Line;

            this._isoLineValues = new List<double>();

            this._LineColorList = new List<Color>();

            this._LineFillColorList = new List<Color>();

            BuildDataset();
            

        }
        

        #region 内部方法

        ///// <summary>
        ///// 将中心点方式转换为框架点方式
        ///// </summary>
        ///// <param name="centerDatas"></param>
        ///// <returns></returns>
        //double[, ,] ComputeIsolineDataValues(double[, ,] centerDatas)
        //{
        //    double[, ,] datas = new double[centerDatas.GetLength(2)+1, centerDatas.GetLength(0)+1 , centerDatas.GetLength(1) + 1];  //z y x

        //    this._isoLineSourceCoors3D = new Coordinate[centerDatas.GetLength(0), centerDatas.GetLength(1), centerDatas.GetLength(2)];
           
        //    //List<double> values = new List<double>();
        //    for (int i = 0; i < this._hyGrid.Grid3DCoordinates.GetLength(0) - 1; i++)  //z轴
        //    {
        //        List<HAMath.InverseDistance.Point3D> points = new List<HAMath.InverseDistance.Point3D>();  //中心点坐标
        //        List<double> values = new List<double>();

        //        for (int j = 0; j < this._hyGrid.Grid3DCoordinates.GetLength(1) - 1; j++)  //y轴
        //        {
        //            for (int k = 0; k < this._hyGrid.Grid3DCoordinates.GetLength(2) - 1; k++)  //x轴
        //            {
        //                HAMath.InverseDistance.Point3D pt = new HAMath.InverseDistance.Point3D(
        //                    this._hyGrid.Grid3DCoordinates[i, j, k].X / 2 + this._hyGrid.Grid3DCoordinates[i , j, k+1].X / 2,
        //                    this._hyGrid.Grid3DCoordinates[i, j, k].Y / 2 + this._hyGrid.Grid3DCoordinates[i, j + 1, k].Y / 2,
        //                    this._hyGrid.Grid3DCoordinates[i, j, k].Z / 2 + this._hyGrid.Grid3DCoordinates[i+1, j, k ].Z);

        //                this._isoLineSourceCoors3D[j, k, i] = new Coordinate(pt.X, pt.Y, pt.Z);

        //                points.Add(pt);

        //                values.Add(centerDatas[j, k, i]);
        //            }
        //        }

        //        for (int j = 0; j < datas.GetLength(1); j++)
        //        {
        //            for (int k = 0; k < datas.GetLength(2); k++)
        //            {
        //                HAMath.InverseDistance.Point3D pt = new HAMath.InverseDistance.Point3D();
        //                pt.X = this._hyGrid.Grid3DCoordinates[i, j, k].X;
        //                pt.Y = this._hyGrid.Grid3DCoordinates[i, j, k].Y;
        //                //网格点z坐标应该是与中心在同一层，相同
        //                pt.Z = this._hyGrid.Grid3DCoordinates[i, j, k].Z / 2 + this._hyGrid.Grid3DCoordinates[i+1, j, k ].Z; // this._hyGrid.Grid3DCoordinates[i, j, k].Z;

        //                double value = HAMath.InverseDistance.InverseDistanceWeight3DScalar.GetPointScalar(pt, points, values);
        //                datas[i, j, k] = value;
        //            }
        //        }
        //    }

            

        //    //for (int i = 0; i < datas.GetLength(0); i++)
        //    //{
        //    //    for (int j = 0; j < datas.GetLength(1); j++)
        //    //    {
        //    //        for (int k = 0; k < datas.GetLength(2); k++)
        //    //        {
        //    //            HAMath.InverseDistance.Point3D pt = new HAMath.InverseDistance.Point3D();
        //    //            pt.X = this._hyGrid.Grid3DCoordinates[i, j, k].X;
        //    //            pt.Y = this._hyGrid.Grid3DCoordinates[i, j, k].Y;
        //    //            pt.Z = this._hyGrid.Grid3DCoordinates[i, j, k].Z;

        //    //            double value = HAMath.InverseDistance.InverseDistanceWeight3DScalar.GetPointScalar(pt, points, values);
        //    //            datas[i, j, k] = value;
        //    //        }
        //    //    }
        //    //}




        //    //for (int k = 0; k < datas.GetLength(0)-1; k++)
        //    //{
        //    //    for (int j = 0; j < centerDatas.GetLength(0); j++)
        //    //    {
        //    //        for (int i = 0; i < centerDatas.GetLength(1); i++)
        //    //        {
        //    //            datas[k, j, i] = centerDatas[j, i, k];
        //    //        }
        //    //        datas[k, j, datas.GetLength(2) - 1] = centerDatas[j, centerDatas.GetLength(1) - 1, k];
        //    //    }
        //    //    for (int i = 0; i < centerDatas.GetLength(1); i++)
        //    //    {
        //    //        datas[k, datas.GetLength(1) - 1, i] = centerDatas[datas.GetLength(1) - 2, i, k];
        //    //    }
        //    //    datas[k, datas.GetLength(1) - 1, datas.GetLength(2) - 1] = centerDatas[datas.GetLength(1) - 2, centerDatas.GetLength(1) - 1, k];

        //    //}

        //    //for (int i = 0; i < datas.GetLength(1); i++)
        //    //{
        //    //    for (int j = 0; j < datas.GetLength(2); j++)
        //    //    {
        //    //        datas[centerDatas.GetLength(2), i, j] = datas[centerDatas.GetLength(2) - 1, i, j];
        //    //    }
        //    //}

        //    return datas;
        //}

        /// <summary>
        /// 转换数据格式 构建插值算法的源信息
        /// </summary>
        /// <returns></returns>
        double[,] TransformDataFormat(Coordinate[,] coords,double[,] values,int[,] ibound)
        {
            int col1Length=coords.GetLength(0);
            int col2Length=coords.GetLength(1);

            int count = 0;
            foreach (int item in ibound)
            {
                if (item != 0)
                    count++;
            }

            double[,] xy = new double[count, 3];

            count = 0;

            for (int i = 0; i < col1Length; i++)
            {
                for (int j = 0; j < col2Length; j++)
                {
                    if (ibound[i, j] == 0)
                        continue;

                    xy[count, 0] = coords[i, j].X;
                    xy[count, 1] = coords[i, j].Y;
                    xy[count, 2] = values[i, j];

                    count++;
                }
            }

            return xy;
        }


        /// <summary>
        /// 计算原始数据坐标
        /// </summary>
        void GenerateSourceDataCoordinates()
        {
            this._isoLineSourceCoors3D = new Coordinate[_isolineSourceDatas.GetLength(0), _isolineSourceDatas.GetLength(1), _isolineSourceDatas.GetLength(2)];
            
            for (int i = 0; i < this._hyGrid.Grid3DCoordinates.GetLength(0) - 1; i++)  //z轴
            {
                for (int j = 0; j < this._hyGrid.Grid3DCoordinates.GetLength(1) - 1; j++)  //y轴
                {
                    for (int k = 0; k < this._hyGrid.Grid3DCoordinates.GetLength(2) - 1; k++)  //x轴
                    {
                        this._isoLineSourceCoors3D[j, k, i] = new Coordinate(
                            (this._hyGrid.Grid3DCoordinates[i, j, k].X + this._hyGrid.Grid3DCoordinates[i, j, k + 1].X) / 2,
                            (this._hyGrid.Grid3DCoordinates[i, j, k].Y + this._hyGrid.Grid3DCoordinates[i, j + 1, k].Y) / 2,
                            (this._hyGrid.Grid3DCoordinates[i, j, k].Z + this._hyGrid.Grid3DCoordinates[i + 1, j, k].Z) / 2
                            );
                    }
                }
            }
        }

        void GenerateReComputedCoordinates()
        {
            int xCount = _hyGrid.ColsCount * 2 + 1, yCount = _hyGrid.RowsCount * 2 + 1, zCount = _hyGrid.LayersCount * 2 + 1;
            this._isolineReComputedCoords3D = new Coordinate[zCount, yCount, xCount];

            int xSource = 0, ySource = 0, zSource = 0;
            bool isXOdd = false, isYOdd = false, isZOdd = false;
            for (int i = 0; i < zCount; i++)  //z轴
            {
                for (int j = 0; j < yCount; j++)  //y轴
                {
                    for (int k = 0; k < xCount; k++)  //x轴
                    {
                        if (isZOdd)
                        {
                            if (isYOdd)
                            {
                                if (isXOdd)
                                {
                                    this._isolineReComputedCoords3D[i, j, k] = new Coordinate(
                                        (this._hyGrid.Grid3DCoordinates[zSource, ySource, xSource].X + this._hyGrid.Grid3DCoordinates[zSource, ySource, xSource + 1].X +
                                        this._hyGrid.Grid3DCoordinates[zSource, ySource + 1, xSource].X + this._hyGrid.Grid3DCoordinates[zSource, ySource + 1, xSource + 1].X +
                                        this._hyGrid.Grid3DCoordinates[zSource + 1, ySource, xSource].X + this._hyGrid.Grid3DCoordinates[zSource + 1, ySource, xSource + 1].X +
                                        this._hyGrid.Grid3DCoordinates[zSource + 1, ySource + 1, xSource].X + this._hyGrid.Grid3DCoordinates[zSource + 1, ySource + 1, xSource + 1].X
                                        ) / 8,
                                        (this._hyGrid.Grid3DCoordinates[zSource, ySource, xSource].Y + this._hyGrid.Grid3DCoordinates[zSource, ySource, xSource + 1].Y +
                                        this._hyGrid.Grid3DCoordinates[zSource, ySource + 1, xSource].Y + this._hyGrid.Grid3DCoordinates[zSource, ySource + 1, xSource + 1].Y +
                                        this._hyGrid.Grid3DCoordinates[zSource + 1, ySource, xSource].Y + this._hyGrid.Grid3DCoordinates[zSource + 1, ySource, xSource + 1].Y +
                                        this._hyGrid.Grid3DCoordinates[zSource + 1, ySource + 1, xSource].Y + this._hyGrid.Grid3DCoordinates[zSource + 1, ySource + 1, xSource + 1].Y
                                        ) / 8,
                                        (this._hyGrid.Grid3DCoordinates[zSource, ySource, xSource].Z + this._hyGrid.Grid3DCoordinates[zSource, ySource, xSource+1].Z +
                                        this._hyGrid.Grid3DCoordinates[zSource, ySource+1, xSource].Z + this._hyGrid.Grid3DCoordinates[zSource, ySource + 1, xSource+1].Z+
                                        this._hyGrid.Grid3DCoordinates[zSource + 1, ySource, xSource].Z + this._hyGrid.Grid3DCoordinates[zSource + 1, ySource, xSource + 1].Z+
                                        this._hyGrid.Grid3DCoordinates[zSource + 1, ySource+1, xSource].Z + this._hyGrid.Grid3DCoordinates[zSource + 1, ySource+1, xSource + 1].Z
                                        ) / 8
                                        );
                                }
                                else
                                {
                                    this._isolineReComputedCoords3D[i, j, k] = new Coordinate(
                                        (this._hyGrid.Grid3DCoordinates[zSource, ySource, xSource].X + this._hyGrid.Grid3DCoordinates[zSource, ySource + 1, xSource].X +
                                        this._hyGrid.Grid3DCoordinates[zSource + 1, ySource, xSource].X + this._hyGrid.Grid3DCoordinates[zSource + 1, ySource + 1, xSource].X) / 4,
                                        (this._hyGrid.Grid3DCoordinates[zSource, ySource, xSource].Y + this._hyGrid.Grid3DCoordinates[zSource, ySource + 1, xSource].Y +
                                        this._hyGrid.Grid3DCoordinates[zSource + 1, ySource, xSource].Y + this._hyGrid.Grid3DCoordinates[zSource + 1, ySource + 1, xSource].Y) / 4,
                                        (this._hyGrid.Grid3DCoordinates[zSource, ySource, xSource].Z + this._hyGrid.Grid3DCoordinates[zSource, ySource + 1, xSource].Z +
                                        this._hyGrid.Grid3DCoordinates[zSource + 1, ySource, xSource].Z + this._hyGrid.Grid3DCoordinates[zSource + 1, ySource + 1, xSource].Z) / 4
                                        );
                                }
                            }
                            else
                            {
                                if (isXOdd)
                                {
                                    this._isolineReComputedCoords3D[i, j, k] = new Coordinate(
                                        (this._hyGrid.Grid3DCoordinates[zSource, ySource, xSource].X + this._hyGrid.Grid3DCoordinates[zSource, ySource, xSource + 1].X +
                                        this._hyGrid.Grid3DCoordinates[zSource + 1, ySource, xSource].X + this._hyGrid.Grid3DCoordinates[zSource + 1, ySource, xSource + 1].X) / 4,
                                        (this._hyGrid.Grid3DCoordinates[zSource, ySource, xSource].Y + this._hyGrid.Grid3DCoordinates[zSource, ySource, xSource + 1].Y +
                                        this._hyGrid.Grid3DCoordinates[zSource + 1, ySource, xSource].Y + this._hyGrid.Grid3DCoordinates[zSource + 1, ySource, xSource + 1].Y) / 4,
                                        (this._hyGrid.Grid3DCoordinates[zSource, ySource, xSource].Z + this._hyGrid.Grid3DCoordinates[zSource, ySource, xSource + 1].Z +
                                        this._hyGrid.Grid3DCoordinates[zSource + 1, ySource, xSource].Z + this._hyGrid.Grid3DCoordinates[zSource + 1, ySource, xSource + 1].Z) / 4
                                        );
                                }
                                else
                                {
                                    this._isolineReComputedCoords3D[i, j, k] = new Coordinate(
                                        (this._hyGrid.Grid3DCoordinates[zSource, ySource, xSource].X + this._hyGrid.Grid3DCoordinates[zSource + 1, ySource, xSource].X) / 2,
                                        (this._hyGrid.Grid3DCoordinates[zSource, ySource, xSource].Y + this._hyGrid.Grid3DCoordinates[zSource + 1, ySource, xSource].Y) / 2,
                                        (this._hyGrid.Grid3DCoordinates[zSource, ySource, xSource].Z + this._hyGrid.Grid3DCoordinates[zSource + 1, ySource, xSource].Z) / 2
                                        );
                                }
                            }
                        }
                        else
                        {
                            if (isYOdd)
                            {
                                if (isXOdd)
                                {
                                    this._isolineReComputedCoords3D[i, j, k] = new Coordinate(
                                        (this._hyGrid.Grid3DCoordinates[zSource, ySource, xSource].X + this._hyGrid.Grid3DCoordinates[zSource, ySource, xSource + 1].X +
                                        this._hyGrid.Grid3DCoordinates[zSource, ySource + 1, xSource].X + this._hyGrid.Grid3DCoordinates[zSource, ySource + 1, xSource + 1].X) / 4,
                                        (this._hyGrid.Grid3DCoordinates[zSource, ySource, xSource].Y + this._hyGrid.Grid3DCoordinates[zSource, ySource, xSource + 1].Y +
                                        this._hyGrid.Grid3DCoordinates[zSource, ySource + 1, xSource].Y + this._hyGrid.Grid3DCoordinates[zSource, ySource + 1, xSource + 1].Y) / 4,
                                        (this._hyGrid.Grid3DCoordinates[zSource, ySource, xSource].Z + this._hyGrid.Grid3DCoordinates[zSource, ySource, xSource + 1].Z +
                                        this._hyGrid.Grid3DCoordinates[zSource, ySource + 1, xSource].Z + this._hyGrid.Grid3DCoordinates[zSource, ySource + 1, xSource + 1].Z) / 4
                                        );
                                }
                                else
                                {
                                    this._isolineReComputedCoords3D[i, j, k] = new Coordinate(
                                        (this._hyGrid.Grid3DCoordinates[zSource, ySource, xSource].X + this._hyGrid.Grid3DCoordinates[zSource, ySource + 1, xSource].X) / 2,
                                        (this._hyGrid.Grid3DCoordinates[zSource, ySource, xSource].Y + this._hyGrid.Grid3DCoordinates[zSource, ySource + 1, xSource].Y) / 2,
                                        (this._hyGrid.Grid3DCoordinates[zSource, ySource, xSource].Z + this._hyGrid.Grid3DCoordinates[zSource, ySource + 1, xSource].Z) / 2
                                        );
                                }
                            }
                            else
                            {
                                if (isXOdd)
                                {
                                    this._isolineReComputedCoords3D[i, j, k] = new Coordinate(
                                        (this._hyGrid.Grid3DCoordinates[zSource, ySource, xSource].X + this._hyGrid.Grid3DCoordinates[zSource, ySource, xSource + 1].X) / 2,
                                        (this._hyGrid.Grid3DCoordinates[zSource, ySource, xSource].Y + this._hyGrid.Grid3DCoordinates[zSource, ySource, xSource + 1].Y) / 2,
                                        (this._hyGrid.Grid3DCoordinates[zSource, ySource, xSource].Z + this._hyGrid.Grid3DCoordinates[zSource, ySource, xSource + 1].Z) / 2
                                        );
                                }
                                else
                                {
                                    this._isolineReComputedCoords3D[i, j, k] = new Coordinate(
                                        this._hyGrid.Grid3DCoordinates[zSource, ySource, xSource].X ,
                                        this._hyGrid.Grid3DCoordinates[zSource, ySource, xSource].Y ,
                                        this._hyGrid.Grid3DCoordinates[zSource, ySource, xSource].Z 
                                        );
                                }
                            }
                        }
                        if (k % 2 != 0)
                        {
                            isXOdd = false;
                            xSource++;
                        }
                        else
                            isXOdd = true;
                    }
                    if (j % 2 != 0)
                    {
                        isXOdd = false;
                        xSource = 0;
                        isYOdd = false;
                        ySource++;
                    }
                    else
                    {
                        isXOdd = false;
                        xSource = 0;
                        isYOdd = true;
                    }
                }
                if (i % 2 != 0)
                {
                    isYOdd = false;
                    ySource = 0;
                    isZOdd = false;
                    zSource++;
                }
                else
                {
                    isYOdd = false;
                    ySource = 0;
                    isZOdd = true;
                }
            }
        }

        /// <summary>
        /// 生成单层所需的IBound(仅用于与重新计算后的网格点相匹配)
        /// </summary>
        int[,] GenerateReComptuedIBound(int[,] iBound)
        {
            if (iBound == null)
                throw new InvalidCastException();
            int length0 = iBound.GetLength(0);
            int length1 = iBound.GetLength(1);

            int[,] newIbound = new int[length0 * 2, length1 * 2];

            for (int i = 0; i < length0; i++)
            {
                for (int j = 0; j < length1; j++)
                {
                    int b = iBound[i, j];
                    newIbound[i * 2, j * 2] = b;
                    newIbound[i * 2 + 1, j*2] = b;
                    newIbound[i * 2 + 1, j * 2 + 1] = b;
                    newIbound[i * 2, j * 2 + 1] = b;
                }
            }

            return newIbound;
        }

        void ComputeIsolineValues(Coordinate[,] targetCoordinate, out double[,] targetValue, double[,] sourceXY)
        {
            int col1Length = targetCoordinate.GetLength(0);
            int col2Length = targetCoordinate.GetLength(1);

            targetValue = new double[col1Length, col2Length];

            alglib.idwbuildmodifiedshepard(sourceXY, sourceXY.GetLength(0), sourceXY.GetLength(1) - 1, _nodalFunctionType, _nq, _nw, out _idwInterPolant);

            for (int i = 0; i < col1Length; i++)
            {
                for (int j = 0; j < col2Length; j++)
                {
                    targetValue[i, j] = alglib.idwcalc(_idwInterPolant, targetCoordinate[i, j].ToArray());
                }
            }
        }


        /// <summary>
        /// 设置无效区
        /// </summary>
        /// <returns></returns>
        bool OnSetInvalidBound()
        {
            try
            {
                switch (_viewMode)
                {
                    case FMAPVIEW.NORMAL:
                        _iBound = new int[_hyGrid.RowsCount, _hyGrid.ColsCount];
                        for (int j = 0; j < _hyGrid.RowsCount; j++)
                        {
                            for (int i = 0; i < _hyGrid.ColsCount; i++)
                            {
                                _iBound[j, i] = _boundary[_viewLayerIndex - 1, j, i];
                            }
                        }



                        break;
                    case FMAPVIEW.FRONT:
                        _iBound = new int[_hyGrid.LayersCount, _hyGrid.ColsCount];
                        for (int k = 0; k < _hyGrid.LayersCount; k++)
                        {
                            for (int i = 0; i < _hyGrid.ColsCount; i++)
                            {
                                _iBound[k, i] = _boundary[k, _viewFrontIndex - 1, i];
                            }
                        }

                        break;
                    case FMAPVIEW.RIGHT:
                        _iBound = new int[_hyGrid.LayersCount, _hyGrid.RowsCount];
                        for (int k = 0; k < _hyGrid.LayersCount; k++)
                        {
                            for (int j = 0; j < _hyGrid.RowsCount; j++)
                            {
                                //_iBound[k, _hyGrid.RowsCount - j - 1] = _boundary[k, j, _viewRightIndex - 1];
                                _iBound[k, j] = _boundary[k,_hyGrid.RowsCount- j-1, _viewRightIndex - 1];
                            }
                        }
                        break;
                    default:
                        break;
                }


            }
            catch 
            { 
                return false;
            }
            return true;
        }

        /// <summary>
        /// 设置等值线源信息
        /// </summary>
        /// <returns></returns>
        bool OnSetIsolineDataInfo()
        {
            bool helpBool = _isGenerateIsolineByCenter;
            if (_hyGrid == null)
                return false;
            if (_isGenerateIsolineByCenter)
            {
                if (
                    _isolineSourceDatas == null ||
                    _isolineSourceDatas.GetLength(2) != _hyGrid.LayersCount ||
                    _isolineSourceDatas.GetLength(0) != _hyGrid.RowsCount ||
                    _isolineSourceDatas.GetLength(1) != _hyGrid.ColsCount
                    )
                {
                    _isolineSourceDatas = null;
                    return false;
                }
            }

            //存储离散点源浓度值
            double[,] sourceValues = null;

            try
            {
                int layerIndex = this.ViewLayerIndex - 1;
                switch (_viewMode)
                {
                    case FMAPVIEW.NORMAL:

                        sourceValues = new double[_hyGrid.RowsCount, _hyGrid.ColsCount];
                        for (int j = 0; j < _hyGrid.RowsCount; j++)
                        {
                            for (int i = 0; i < _hyGrid.ColsCount; i++)
                            {
                                sourceValues[j, i] = _isolineSourceDatas[j, i, layerIndex];
                            }
                        }


                        break;
                    case FMAPVIEW.FRONT:

                        sourceValues = new double[_hyGrid.LayersCount, _hyGrid.ColsCount];
                        for (int k = 0; k < _hyGrid.LayersCount; k++)
                        {
                            for (int i = 0; i < _hyGrid.ColsCount; i++)
                            {
                                sourceValues[k, i] = _isolineSourceDatas[layerIndex, i, k];
                            }
                        }

                        break;
                    case FMAPVIEW.RIGHT:

                        sourceValues = new double[_hyGrid.LayersCount, _hyGrid.RowsCount];
                        for (int k = 0; k < _hyGrid.LayersCount; k++)
                        {
                            for (int j = 0; j < _hyGrid.RowsCount; j++)
                            {
                                sourceValues[k, j] = _isolineSourceDatas[_hyGrid.RowsCount - j - 1, layerIndex, k];
                            }
                        }

                        //_grid2DCoords = new Coordinate[_hyGrid.LayersCount, _hyGrid.RowsCount];

                        //    for (int i = 0; i < _hyGrid.LayersCount; i++)
                        //    {
                        //        for (int j = 0; j < _hyGrid.RowsCount; j++)
                        //        {
                        //            coord = _isoLineSourceCoors3D[j, layerIndex, i];
                        //            _grid2DCoords[i, j] = new Coordinate(coord.Y, coord.Z);
                        //        }
                        //    }

                        break;
                    default:
                        break;
                }
            }
            catch
            {
                return false;
            }
            if (_isGenerateIsolineByCenter)
            {
                _isoLineDataInfo = sourceValues;
                return true;
            }

            try
            {
                double[,] xy = null;
                int layerIndex = this.ViewLayerIndex - 1;

                switch (_viewMode)
                {
                    case FMAPVIEW.NORMAL:
                        //通过置标志位取得想要的数据
                        _isGenerateIsolineByCenter = true;
                        xy = TransformDataFormat(Grid2DCoords, sourceValues,IBound);
                        //取得数据后置回原始状态
                        _isGenerateIsolineByCenter = false;

                        this.ComputeIsolineValues(Grid2DCoords,out _isoLineDataInfo,xy);

                        break;
                    case FMAPVIEW.FRONT:
                        //通过置标志位取得想要的数据
                        _isGenerateIsolineByCenter = true;
                        xy = TransformDataFormat(Grid2DCoords, sourceValues,IBound);
                        //取得数据后置回原始状态
                        _isGenerateIsolineByCenter = false;

                        this.ComputeIsolineValues(Grid2DCoords, out _isoLineDataInfo, xy);


                        break;
                    case FMAPVIEW.RIGHT:
                        //通过置标志位取得想要的数据
                        _isGenerateIsolineByCenter = true;
                        xy = TransformDataFormat(Grid2DCoords, sourceValues,IBound);
                        //取得数据后置回原始状态
                        _isGenerateIsolineByCenter = false;

                        this.ComputeIsolineValues(Grid2DCoords, out _isoLineDataInfo, xy);


                        break;
                    default:
                        break;
                }

                _iBoundComputed = this.GenerateReComptuedIBound(_iBound);

                int length1 = _iBoundComputed.GetLength(0);
                int length2 = _iBoundComputed.GetLength(1);

                for (int i = 0; i < length1; i++)
                {
                    for (int j = 0; j < length2; j++)
                    {
                        if (i == 0)
                        {
                            if (j == 0)
                            {
                                if (_iBoundComputed[i, j] == 0)
                                {
                                    _isoLineDataInfo[i, j] = sourceValues[i/2, j/2];
                                }
                            }
                            else if (j == length2)
                            {
                                if (_iBoundComputed[i, j] == 0)
                                {
                                    _isoLineDataInfo[i, j + 1] = sourceValues[i/2, j/2];
                                }
                            }
                            else
                            {
                                if (_iBoundComputed[i, j] == 0 && _iBoundComputed[i, j - 1] == 0)
                                    _isoLineDataInfo[i, j] = sourceValues[i/2, j/2];
                            }
                        }
                        else if (i == length1)
                        {
                            if (j == 0)
                            {
                                if (_iBoundComputed[i, j] == 0)
                                {
                                    _isoLineDataInfo[i + 1, j] = sourceValues[i/2, j/2];
                                }
                            }
                            else if (j == length2)
                            {
                                if (_iBoundComputed[i, j] == 0)
                                {
                                    _isoLineDataInfo[i + 1, j + 1] = sourceValues[i/2, j/2];
                                }
                            }
                            else
                            {
                                if (_iBoundComputed[i, j] == 0 && _iBoundComputed[i, j - 1] == 0)
                                    _isoLineDataInfo[i + 1, j] = sourceValues[i/2, j/2];
                            }
                        }
                        else if (j == 0)
                        {
                            if (_iBoundComputed[i, j] == 0 && _iBoundComputed[i - 1, j] == 0)
                                _isoLineDataInfo[i, j] = sourceValues[i/2, j/2];
                        }
                        else if (j == length2)
                        {
                            if (_iBoundComputed[i, j] == 0 && _iBoundComputed[i - 1, j] == 0)
                                _isoLineDataInfo[i, j + 1] = sourceValues[i/2, j + 1/2];
                        }
                        else if (_iBoundComputed[i, j] == 0 && _iBoundComputed[i - 1, j] == 0 && _iBoundComputed[i - 1, j - 1] == 0 && _iBoundComputed[i, j - 1] == 0)
                        {
                            _isoLineDataInfo[i, j] = sourceValues[i/2, j/2];
                        }
                    }
                }
            }
            catch(Exception e)
            {
                _isGenerateIsolineByCenter = helpBool;
                return false;
            }
            return true;
        }


        protected override void OnViewModeChanged()
        {
            if (this.HyGrid != null)
            {
                this.Redraw();
            }
        }


        //private void SetLabelFont()
        //{
        //    if (this._grid2DCoords == null) return;

        //    double length = 0;

        //    length = Math.Max(Math.Abs(this._grid2DCoords[this._grid2DCoords.GetLength(0) - 1, this._grid2DCoords.GetLength(1) - 1].X - this._grid2DCoords[0, 0].X),
        //        Math.Abs(this._grid2DCoords[this._grid2DCoords.GetLength(0) - 1, this._grid2DCoords.GetLength(1) - 1].Y - this._grid2DCoords[0, 0].Y));

        //    float size = (float)(length / 50);

        //    this.LabelFont = new Font("Times New Roman", size);

        //}

        #endregion

        
        #region 公共方法
                
        public void ResetGridData(HyGrid grid, List<int[,]> boundary)
        {
            _hyGrid = grid;
            if (_hyGrid == null)
            {
                _boundary = null;
                return;
            }
            if (boundary == null || boundary.Count <= 0)
            {
                return;
            }
            else
            {
                this.GenerateReComputedCoordinates();
                this._boundary = GetNeededGridInfo.TranslateList2DTo3D(_hyGrid, boundary);
            }

            //this.SetLabelFont();
            this.Update();

        }

        public override bool OpenLayer()
        {
            this.BuildDataset();

            this.Render();

            //刘加， 当打开图层时，将图层属性传到绘制图层
            this.CopyParaToLayer();

            this.Redraw();

            return true;
        }

        /// <summary>
        /// 传属性到绘制图层
        /// </summary>
        private void CopyParaToLayer()
        {
            if (this.ILayer == null) return;
            Map6IsolineLayer layer = this.ILayer as Map6IsolineLayer;
            if (layer == null) return;
            //复制标注属性
            layer.IsShowLabel = this.IsShowLabel;
            layer.LabelColor = this.LabelColor;
            layer.LabelFont = this.LabelFont;
            layer.LabelNum = this.LabelNum;
            layer.LableFormatNum = this.LableFormatNum;
            layer.StepNum = this.StepNum;
            
            //复制图例属性

            //复制面属性
            layer.IsShowContourFill = this.IsShowContourFill;
            //复线属性
            layer.IsLineVisble = this.IsLineVisble;
            layer.LineWidth = this.LineWidth;
            layer.LineColor = this.LineColor;
            
        }


        public override void Render()
        {
            //base.Render();
            //添加图层
            this._iLayer = new Map6IsolineLayer();

            this.dataSet = this._iLayer.DataSet as DataSet ;
            this._defaultManager.CurrentMap.Layers.Add(this._iLayer);
            
            //该图层在Gis图层中的添加位置  保加
            if (this._mapLayerIndex != -1)
            {
                this._iLayer.LockDispose();

                this.DefaultManager.CurrentMap.Layers.Remove(this._iLayer);

                this.DefaultManager.CurrentMap.Layers.Insert(this._mapLayerIndex, this._iLayer);

                this._iLayer.UnlockDispose();

                this._mapLayerIndex = -1;
            }

            this._isLoaded = true;

            _iLayer.SelectionEnabled = false;
            
            this.OnSetVisible();

            //刘加
            this._defaultManager.CurrentMap.Paint += new PaintEventHandler(this.OnPaint);  //要记得关闭图层时移除事件

        }

        public override void Redraw()
        {
            //(this._dataSet as FeatureSet).Features.Clear();
            if (_iLayer == null) return;

            //if (_boundary == null || _boundary.Length <= 0)
            //{
            //    _iLayer.Invalidate();
            //    return;
            //}

            if (_isoLineValues.Count <= 0)
            {
                (_iLayer as Map6IsolineLayer).ContourLineList.Clear();

                _iLayer.Invalidate();
                return;
            }

            //修正超出范围的值
            //double maxValue = this._isoLineValues.Max();
            //double minValue = this._isoLineValues.Min();

            double[,] isolineValue = IsolineDataInfo;
            if (isolineValue == null)
            {
                (_iLayer as Map6IsolineLayer).SetData(Grid2DCoords, isolineValue, _iBound, Rotation, !_isGenerateIsolineByCenter);
                _iLayer.Invalidate();
                return;
            }

            for (int i = 0; i < isolineValue.GetLength(0); i++)
            {
                for (int j = 0; j < isolineValue.GetLength(1); j++)
                {
                    isolineValue[i, j] = Math.Round(isolineValue[i, j], 4);
                    if (isolineValue[i, j] > this._maxSourceData)
                        isolineValue[i, j] = this._maxSourceData;
                    else if (isolineValue[i, j] < this._minSourceData)
                        isolineValue[i, j] = this._minSourceData;
                }
            }

            if (!_isGenerateIsolineByCenter)
                _iBoundComputed = GenerateReComptuedIBound(_iBound);
            else
                _iBoundComputed = _iBound;
            if (!(_iLayer as Map6IsolineLayer).SetData(Grid2DCoords, isolineValue, _iBoundComputed, Rotation, !_isGenerateIsolineByCenter))
            {
                _iLayer.Invalidate();
                return;
            }           
            (_iLayer as Map6IsolineLayer).ContourLineList = this.ContourLineList;

            _iLayer.Invalidate();
        }

        public override bool SaveLayer()
        {
            return base.SaveLayer();
        }

        /// <summary>
        /// 刘加
        /// </summary>
        public override void StopRender()
        {
            base.StopRender();
            this._defaultManager.CurrentMap.Paint -= new PaintEventHandler(this.OnPaint);
        }


        protected override void OnSetVisible()
        {
            if (this.ILayer != null)
            {
                (this.ILayer as Map6IsolineLayer).IsVisible = this.Visible;
            }
        }

        #endregion

        
        #region 数据属性及字段

        int _nodalFunctionType;

        public int NodalFunctionType
        {
            get { return _nodalFunctionType; }
            set { _nodalFunctionType = value; }
        }

        int _nq;

        public int Nq
        {
            get { return _nq; }
            set { _nq = value; }
        }

        int _nw;

        public int Nw
        {
            get { return _nw; }
            set { _nw = value; }
        }



        [NonSerialized]
        alglib.idwinterpolant _idwInterPolant;
        /// <summary>
        /// 等值线插值模型 
        /// </summary>
        public alglib.idwinterpolant IdwInterPolant
        {
            get { return _idwInterPolant; }
        }


        bool _isGenerateIsolineByCenter = false;
        /// <summary>
        /// 生成等值线方式
        /// </summary>
        public bool IsGenerateIsolineByCenter
        {
            get { return _isGenerateIsolineByCenter; }
            set
            {
                _isGenerateIsolineByCenter = value;
                this.Redraw();
            }
        }



        Coordinate[,] _grid2DCoords;
        /// <summary>
        /// 二维网格点坐标
        /// </summary>
        Coordinate[,] Grid2DCoords
        {
            get
            {
                if (_hyGrid == null)
                    return null;

                Coordinate coord = null;
                int layerIndex = this.ViewLayerIndex-1;
                switch (_viewMode)
                {
                    case FMAPVIEW.NORMAL:
                        if (_isGenerateIsolineByCenter)
                        {
                            _grid2DCoords = new Coordinate[_hyGrid.RowsCount, _hyGrid.ColsCount];

                            for (int i = _hyGrid.RowsCount - 1; i >= 0; i--)
                            {
                                for (int j = 0; j < _hyGrid.ColsCount; j++)
                                {
                                    _grid2DCoords[i, j] = _isoLineSourceCoors3D[i, j, layerIndex];
                                }
                            }
                        }
                        else
                        {
                            _grid2DCoords = new Coordinate[_hyGrid.RowsCount * 2 + 1, _hyGrid.ColsCount * 2 + 1];

                            for (int i = _hyGrid.RowsCount * 2; i >= 0; i--)
                            {
                                for (int j = 0; j < _hyGrid.ColsCount * 2 + 1; j++)
                                {
                                    _grid2DCoords[i, j] = this._isolineReComputedCoords3D[layerIndex * 2, i, j];
                                }
                            }
                        }
                        return _grid2DCoords;

                    case FMAPVIEW.FRONT:
                        if (_isGenerateIsolineByCenter)
                        {
                            _grid2DCoords = new Coordinate[_hyGrid.LayersCount, _hyGrid.ColsCount];

                            for (int i = 0; i < _hyGrid.LayersCount; i++)
                            {
                                for (int j = 0; j < _hyGrid.ColsCount; j++)
                                {
                                    coord = _isoLineSourceCoors3D[layerIndex, j, i];
                                    _grid2DCoords[i, j] = new Coordinate(coord.X, coord.Z);
                                }
                            }
                        }
                        else
                        {
                            _grid2DCoords = new Coordinate[_hyGrid.LayersCount * 2 + 1, _hyGrid.ColsCount * 2 + 1];

                            for (int i = 0; i < _hyGrid.LayersCount * 2 + 1; i++)
                            {
                                for (int j = 0; j < _hyGrid.ColsCount * 2 + 1; j++)
                                {
                                    coord = _isolineReComputedCoords3D[i, layerIndex * 2, j];
                                    _grid2DCoords[i, j] = new Coordinate(coord.X, coord.Z);
                                }
                            }
                        }

                        return _grid2DCoords;

                    case FMAPVIEW.RIGHT:
                        if (_isGenerateIsolineByCenter)
                        {
                            _grid2DCoords = new Coordinate[_hyGrid.LayersCount, _hyGrid.RowsCount];

                            for (int i = 0; i < _hyGrid.LayersCount; i++)
                            {
                                for (int j = 0; j < _hyGrid.RowsCount; j++)
                                {
                                    coord = _isoLineSourceCoors3D[_hyGrid.RowsCount - j - 1, layerIndex, i];
                                    _grid2DCoords[i, j] = new Coordinate(coord.Y, coord.Z);
                                }
                            }
                        }
                        else
                        {
                            _grid2DCoords = new Coordinate[_hyGrid.LayersCount * 2 + 1, _hyGrid.RowsCount * 2 + 1];

                            for (int i = 0; i < _hyGrid.LayersCount * 2 + 1; i++)
                            {
                                for (int j = 0; j < _hyGrid.RowsCount * 2 + 1; j++)
                                {
                                    coord = _isolineReComputedCoords3D[i, _hyGrid.RowsCount * 2 - j, layerIndex * 2];
                                    _grid2DCoords[i, j] = new Coordinate(coord.Y, coord.Z);
                                }
                            }
                        }

                        return _grid2DCoords;

                    default:
                        return null;
                }
            }
        }


        double Rotation
        {
            get
            {
                if (_hyGrid == null)
                    return 0;

                switch (_viewMode)
                {
                    case FMAPVIEW.NORMAL:
                        return _hyGrid.RotationZ;
                    case FMAPVIEW.FRONT:
                        return 0;
                    case FMAPVIEW.RIGHT:
                        return 0;
                    default:
                        return 0;
                }
            }
        }

        int[,] _iBoundComputed;
        /// <summary>
        /// 计算后的ibound
        /// </summary>
        public int[,] IBoundComputed
        {
            get { return _iBoundComputed; }
            set { _iBoundComputed = value; }
        }


        int[,] _iBound;
        /// <summary>
        /// 原始ibound
        /// </summary>
        public int[,] IBound
        {
            get 
            {
                OnSetInvalidBound();
                return _iBound; 
            }
        }

        int _viewLayerIndex = 1;
        int _viewFrontIndex = 1;
        int _viewRightIndex = 1;
        /// <summary>
        /// 索引从1开始
        /// </summary>
        public int ViewLayerIndex
        {
            get
            {
                switch (_viewMode)
                {
                    case FMAPVIEW.NORMAL:
                        return _viewLayerIndex > 1 ? _viewLayerIndex : 1;
                    case FMAPVIEW.FRONT:
                        return _viewFrontIndex > 1 ? _viewFrontIndex : 1;
                    case FMAPVIEW.RIGHT:
                        return _viewRightIndex > 1 ? _viewRightIndex : 1;
                    default:
                        return 1;
                }
            }
            set
            {
                if (value <= 0) return;
                switch (_viewMode)
                {
                    case FMAPVIEW.NORMAL:
                        if (value == _viewLayerIndex || value > _hyGrid.LayersCount) return;
                        _viewLayerIndex = value;

                        break;
                    case FMAPVIEW.FRONT:
                        if (value == _viewFrontIndex || value > _hyGrid.RowsCount) return;
                        _viewFrontIndex = value;
                        break;
                    case FMAPVIEW.RIGHT:
                        if (value == _viewRightIndex || value > _hyGrid.ColsCount) return;
                        _viewRightIndex = value;
                        break;
                    default:
                        return;
                }
                if (this.IsLoaded)
                {
                    //falseIsolineValueMethod();
                    this.Redraw();
                }
            }
        }

        int[, ,] _boundary;
        /// <summary>
        /// 网格单元有效性
        /// </summary>
        public int[, ,] Boundary
        {
            get { return _boundary; }

            set
            {
                this._boundary = value;
                //OnSetInvalidBound();
                //if (this.IsLoaded)
                //{
                //    this.Redraw();
                //}
            }

        }

        [NonSerialized]
        double[,] _isoLineDataInfo;
        /// <summary>
        /// 绘等值线使用的数据（比如浓度值）
        /// </summary>
        public double[,] IsolineDataInfo
        {
          get 
          { 
              if(! OnSetIsolineDataInfo())
                  return null;
              return _isoLineDataInfo; 
          }
        }

        Coordinate[, ,] _isolineReComputedCoords3D;
        /// <summary>
        /// 网格边框及中心点形成的新网格坐标Z,Y,X
        /// </summary>
        public Coordinate[, ,] IsolineReComputedCoords3D
        {
            get { return _isolineReComputedCoords3D; }
            set { _isolineReComputedCoords3D = value; }
        }


        Coordinate[, ,] _isoLineSourceCoors3D;
        /// <summary>
        /// 网格中心点坐标Y,X,Z
        /// </summary>
        public Coordinate[, ,] IsoLineSourceCoors3D
        {
            get { return _isoLineSourceCoors3D; }
            set { _isoLineSourceCoors3D = value; }
        }


        double[, ,] _isolineSourceDatas;
        /// <summary>
        /// 网格中心点数据（比如浓度值）
        /// 刘加这一句：在值这个数据前，必须先传无效值。因为在这里求数据最大最小值时要去掉无效值
        /// </summary>
        public double[, ,] IsolineSourceDatas
        {
            set 
            { 
                _isolineSourceDatas = value;
                this.GenerateSourceDataCoordinates();

                this._maxSourceData = double.MinValue;
                this._minSourceData = double.MaxValue;


                for(int i=0;i<value .GetLength (0);i++)
                {
                    for (int j = 0; j < value.GetLength(1); j++)
                    {
                        for (int k = 0; k < value.GetLength(2); k++)
                        {
                            if (value[i,j,k] > this._maxSourceData && this._boundary[k,i,j]==1) //求数据最大最小值时还要考虑ibound
                            {
                                if (value[i, j, k] != this.InvalidValue)
                                {
                                    this._maxSourceData = value[i, j, k];
                                }
                            }
                            if (value[i, j, k] < this._minSourceData && this._boundary[k, i, j] == 1)
                            {
                                if (value[i, j, k] != this.InvalidValue)
                                {
                                    this._minSourceData = value[i, j, k];
                                }
                            }
                        }
                    }
                }


                //foreach (double data in value)
                //{
                //    if (data > this._maxSourceData)
                //    {
                //        if (data != -999)
                //        {
                //            this._maxSourceData = data;
                //        }
                //    }
                //    if (data < this._minSourceData)
                //    {
                //        if (data != -999)
                //        {
                //            this._minSourceData = data;
                //        }
                //    }
                //}

                //_isolineDataInfoes = ComputeIsolineDataValues(_isolineSourceDatas);
                //_isolineDataInfoes = ComputeIsolineValues();
            }
        }


        double _minSourceData = double.MaxValue;

        /// <summary>
        /// 原始浓度值最大值
        /// </summary>
        public double MinSourceData
        {
            get { return _minSourceData; }
            set { _minSourceData = value; }
        }


        double _maxSourceData = double.MinValue;

        /// <summary>
        /// 原始浓度值最小值
        /// </summary>
        public double MaxSourceData
        {
            get { return _maxSourceData; }
            set { _maxSourceData = value; }
        }


        double _invalidValue = -999;

        /// <summary>
        /// 数据无效值。这个值必须在传数据前赋值，因为在传数据时要 求数据最大最小值，需考虑无效值的影响
        /// </summary>
        public double InvalidValue
        {
            get { return _invalidValue; }
            set { _invalidValue = value; }
        }




        HyGrid _hyGrid;

        public HyGrid HyGrid
        {
            get { return _hyGrid; }
            set
            {
                _hyGrid = value;
                this.GenerateReComputedCoordinates();
                //this.SetLabelFont();
            }
        }





        private List<double> _isoLineValues;

        /// <summary>
        /// 等值线值信息
        /// </summary>
        public List<double> IsoLineValues
        {
            get { return _isoLineValues; }
            set { _isoLineValues = value; }
        }


        List<ContourLine> _contourLineList = new List<ContourLine>();

        public List<ContourLine> ContourLineList
        {
            get { return _contourLineList; }
            set 
            {
                _contourLineList = value;

                if (this._isLoaded == false) return;

                if (this.ILayer != null)
                {
                    (this.ILayer as Map6IsolineLayer).ContourLineList = value;
                }

            }
        }
        

        public void SetContourLineList()
        {
            //if (_isoLineValues == null || _isoLineValues.Count <= 0) return;

            this._contourLineList = new List<ContourLine>();

            if (this.ILayer != null)
                (this.ILayer as Map6IsolineLayer).ContourLineList.Clear();

            for (int i = 0; i < _isoLineValues.Count; i++)
            {
                ContourLine cl = new ContourLine();
                cl.ContourLineValue = _isoLineValues[i];
                cl.ContourLineColor = this._LineColorList[i];
                cl.ContourLineFillColor = this._LineFillColorList[i];
                this._contourLineList.Add(cl);

                if (this.ILayer != null)
                    (this.ILayer as Map6IsolineLayer).ContourLineList.Add(cl);

            }

            //List<System.Drawing.Color> ContourLineColorList = new List<System.Drawing.Color>();
            //List<System.Drawing.Color> ContourLineFillColorList = new List<System.Drawing.Color>();

            //ContourLineColorList = MyArithmetic.BuildColor(this._LineColorList);
            //ContourLineFillColorList = MyArithmetic.BuildColor(this._LineFillColorList);
            //for (int i = 0; i < this._contourLineList.Count; i++)
            //{
            //    this._contourLineList[i].ContourLineColor = ContourLineColorList[MyArithmetic.GetColorPos(ContourLineColorList.Count, i, this._contourLineList.Count,
            //        this._contourLineList[0].ContourLineValue, this._contourLineList[this._contourLineList.Count - 1].ContourLineValue)];
            //    this._contourLineList[i].ContourLineFillColor = ContourLineFillColorList[MyArithmetic.GetColorPos(ContourLineFillColorList.Count, i, this._contourLineList.Count,
            //        this._contourLineList[0].ContourLineValue, this._contourLineList[this._contourLineList.Count - 1].ContourLineValue)];
            //}
            
        }
        

        #endregion

        
        # region 显示属性

        # region 线颜色与添充颜色

        private List<System.Drawing.Color> _LineColorList;

        /// <summary>
        /// 等值线颜色信息
        /// </summary>
        public List<System.Drawing.Color> LineColorList
        {
            get { return _LineColorList; }
            set { _LineColorList = value; }
        }


        private List<System.Drawing.Color> _LineFillColorList;

        /// <summary>
        /// 等值线填充颜色信息
        /// </summary>
        public List<System.Drawing.Color> LineFillColorList
        {
            get { return _LineFillColorList; }
            set { _LineFillColorList = value; }
        }

        # endregion


        # region 标注属性


        private bool _isShowLabel = true;

        /// <summary>
        /// 是否显示标注
        /// </summary>
        public bool IsShowLabel
        {
            get { return _isShowLabel; }
            set 
            {
                _isShowLabel = value;
                if (this._isReadyRedraw == false) return;
                if (this._iLayer != null)
                {
                    (this._iLayer as Map6IsolineLayer).IsShowLabel = value;
                }
            }
        }


        private Color _labelColor = System.Drawing.Color.Black;  //标注颜色设置

        /// <summary>
        /// 标注颜色
        /// </summary>
        public Color LabelColor
        {
            get { return _labelColor; }
            set 
            { 
                _labelColor = value;
                if (this._isReadyRedraw == false) return;
                if (this._iLayer != null)
                {
                    (this._iLayer as Map6IsolineLayer).LabelColor = value;
                }
            }
        }
         

        private System.Drawing.Font _labelFont = new Font("Times New Roman", 12.0F); 

        /// <summary>
        /// 标注字体
        /// </summary>
        public System.Drawing.Font LabelFont
        {
            get { return _labelFont; }
            set
            {
                _labelFont = value;
                if (this._isReadyRedraw == false) return;
                if (this._iLayer != null)
                {
                    (this._iLayer as Map6IsolineLayer).LabelFont = value;
                }
            }
        }

        private bool _isLabelTextFormat = false;

        /// <summary>
        /// 标注字符串是否格式化
        /// </summary>
        public bool IsLabelTextFormat
        {
            get { return _isLabelTextFormat; }
            set 
            {
                _isLabelTextFormat = value;
                if (this._isReadyRedraw == false) return;
                if (this._iLayer != null)
                {
                    (this._iLayer as Map6IsolineLayer).IsLabelTextFormat = value;
                }

            }
        }


        private Int64 _lableFormatNum = 2; 

        /// <summary>
        /// //等值线标注小数点位数
        /// </summary>
        public Int64 LableFormatNum
        {
            get { return _lableFormatNum; }
            set 
            { 
                _lableFormatNum = value;
                if (this._isReadyRedraw == false) return;
                if (this._iLayer != null)
                {
                    (this._iLayer as Map6IsolineLayer).LableFormatNum = value;
                }
            }
        }



        private int _stepNum = 20; 

        /// <summary>
        /// 标注间距为20个网格
        /// </summary>
        public int StepNum
        {
            get { return _stepNum; }
            set 
            { 
                _stepNum = value;
                if (this._isReadyRedraw == false) return;
                if (this._iLayer != null)
                {
                    (this._iLayer as Map6IsolineLayer).StepNum = value;
                }
            }
        }



        private int _labelNum = 10;  

        /// <summary>
        /// //标注个数最大为10个
        /// </summary>
        public int LabelNum
        {
            get { return _labelNum; }
            set 
            {
                _labelNum = value;
                if (this._isReadyRedraw == false) return;
                if (this._iLayer != null)
                {
                    (this._iLayer as Map6IsolineLayer).LabelNum = value;
                }
            }
        }



        # endregion


        # region 面属性

        private bool _isShowContourFill = true;  

        /// <summary>
        /// 是否显示添充
        /// </summary>
        public bool IsShowContourFill
        {
            get { return _isShowContourFill; }
            set 
            {
                _isShowContourFill = value;
                if (this._isReadyRedraw == false) return;
                if (this._iLayer != null)
                {
                    (this._iLayer as Map6IsolineLayer).IsShowContourFill = value;
                }
            }
        }

        # endregion


        # region 线属性

        private bool _isLineVisble = true;  

        /// <summary>
        /// 是否显示等值线
        /// </summary>
        public bool IsLineVisble
        {
            get { return _isLineVisble; }
            set 
            { 
                _isLineVisble = value;
                if (this._isReadyRedraw == false) return;
                if (this._iLayer != null)
                {
                    (this._iLayer as Map6IsolineLayer).IsLineVisble = value;
                }
            }
        }


        private int _lineWidth = 1; 

        /// <summary>
        /// //线宽
        /// </summary>
        public int LineWidth
        {
            get { return _lineWidth; }
            set
            { 
                _lineWidth = value;
                if (this._isReadyRedraw == false) return;
                if (this._iLayer != null)
                {
                    (this._iLayer as Map6IsolineLayer).LineWidth = value;
                }
            }
        }

        private Color _lineColor = Color.Black;  //

        /// <summary>
        /// 线颜色。是统一设置还是可渐变设置？？？？？
        /// </summary>
        public Color LineColor
        {
            get { return _lineColor; }
            set
            {
                _lineColor = value;
                if (this._isReadyRedraw == false) return;
                if (this._iLayer != null)
                {
                    (this._iLayer as Map6IsolineLayer).LineColor = value;
                }
            }
        }

        
        # endregion


        # region 图例字段

        private bool _IsShowLegend = true; 

        /// <summary>
        /// 是否显示图例
        /// </summary>
        public bool IsShowLegend
        {
            get { return _IsShowLegend; }
            set 
            { 
                _IsShowLegend = value;
            }
        }

        private System.Drawing.Font _legendFont = new Font("Times New Roman", 8.0F); 

        /// <summary>
        /// 图例字体
        /// </summary>
        public System.Drawing.Font LegendFont
        {
            get { return _legendFont; }
            set { _legendFont = value; }
        }

        private System.Drawing.Color _legendColor = System.Drawing.Color.Red;

        /// <summary>
        /// 图例颜色
        /// </summary>
        public System.Drawing.Color LegendColor
        {
            get { return _legendColor; }
            set { _legendColor = value; }
        }

        private bool _IsLegendTextFormat = false; 

        /// <summary>
        /// 是否启用图例文本格式化
        /// </summary>
        public bool IsLegendTextFormat
        {
            get { return _IsLegendTextFormat; }
            set { _IsLegendTextFormat = value; }
        }

        private int _LegendFormatNum = 1; 

        /// <summary>
        /// 图例小数点位数
        /// </summary>
        public int LegendFormatNum
        {
            get { return _LegendFormatNum; }
            set { _LegendFormatNum = value; }
        }

        private double _LegendOffsetX = 0; //

        /// <summary>
        /// 图例X方向偏移量
        /// </summary>
        public double LegendOffsetX
        {
            get { return _LegendOffsetX; }
            set 
            { _LegendOffsetX = value; }
        }

        private double _LegendOffsetY = 0; 

        /// <summary>
        /// 图例Y方向偏移量
        /// </summary>
        public double LegendOffsetY
        {
            get { return _LegendOffsetY; }
            set { _LegendOffsetY = value; }
        }

        private Color _legendBackColor = Color.White;  

        /// <summary>
        /// 背景颜色
        /// </summary>
        public Color LegendBackColor
        {
            get { return _legendBackColor; }
            set { _legendBackColor = value; }
        }

        private float _legendWidth = 10.0f;  

        /// <summary>
        /// 图例宽度
        /// </summary>
        public float LegendWidth
        {
            get { return _legendWidth; }
            set { _legendWidth = value; }
        }

        private float _legendHeight = 0.5f;  

        /// <summary>
        /// 图例高占窗口的百分比
        /// </summary>
        public float LegendHeight
        {
            get { return _legendHeight; }
            set { _legendHeight = value; }
        }

        private bool _useLayerLegend = false;

        public bool UseLayerLegend
        {
            get { return _useLayerLegend; }
            set
            {
                _useLayerLegend = value;
                if (this._isReadyRedraw == false) return;
                if (this.ILayer != null)
                {
                    (this.ILayer as Map6IsolineLayer).UseLayerLegend = value;
                    if (value == true)
                    {
                        this.CopyLegendParaToLayer();
                    }
                    
                    //this.DefaultManager.CurrentMap.Refresh();
                    this.ILayer.Invalidate();
                }

            }
        }

        # endregion


        # endregion



        # region 绘制图例 ，刘加

        private void OnPaint(object sender, PaintEventArgs e)
        {
            if (this._IsShowLegend == true)
            {
                this.DrawLegend(e.Graphics);
            }
        }

        private void CopyLegendParaToLayer()
        {
            if (this.ILayer == null) return;
            Map6IsolineLayer layer = this.ILayer as Map6IsolineLayer;
            if (layer == null) return;

            layer.IsShowLegend = this.IsShowLegend;
            layer.LegendBackColor = this.LegendBackColor;
            layer.LegendColor = this.LegendColor;
            layer.LegendFont = this.LegendFont;
            layer.LegendFormatNum = this.LegendFormatNum;
            layer.LegendHeight = this.LegendHeight;
            layer.LegendOffsetX = this.LegendOffsetX;
            layer.LegendOffsetY = this.LegendOffsetY;
            layer.LegendWidth = this.LegendWidth;
            layer.IsLegendTextFormat = this.IsLegendTextFormat;

        }


        /// <summary>
        /// 在窗体上绘制图例
        /// </summary>
        /// <param name="g"></param>
        private void DrawLegend(Graphics g)
        {
            //this._legendFont = new Font("Times New Roman", 8.0F); //图例Font

            if (this._contourLineList == null) return;
            if (this._contourLineList.Count <= 0) return;
            if (this.Visible == false) return;
            if (this._IsShowLegend == false) return;


            float Xmax = this.DefaultManager.CurrentMap.Width;  // .Right;

            float Ymax = this.DefaultManager.CurrentMap.Height;  //.Bottom;

            float Ymin = 0;  // this.m_ParenLManager.CurrentMap.Top;

            float h = (Ymax - Ymin - 20) * this._legendHeight;

            double stepY = h / this._contourLineList.Count;

            //画背景
            PointF f1 = new PointF();
            f1.X = (float)this._LegendOffsetX; // Xmax - this._legendWidth - 10.0f -
                // (float)g.MeasureString(this._contourLineList[this._contourLineList.Count - 1].ContourLineValue.ToString(), this._legendFont).Width + (float)this._LegendOffsetX;
            f1.Y = Ymin + (float)this._LegendOffsetY;

            PointF f2 = new PointF();
            f2.X = f1.X + this._legendWidth + (float)g.MeasureString(this._contourLineList[this._contourLineList.Count - 1].ContourLineValue.ToString(), this._legendFont).Width;
            f2.Y = f1.Y;

            PointF f3 = new PointF();
            f3.X = f2.X;
            f3.Y = f1.Y + (float)h;

            PointF f4 = new PointF();
            f4.X = f1.X;
            f4.Y = f3.Y;

            Region region = new Region(new RectangleF(f1.X, f1.Y, f3.X - f1.X, f3.Y - f1.Y));

            //g.FillRegion(new SolidBrush(this._legendBackColor), region);


            //直接用屏幕坐标绘制图例
            for (int i = this.ContourLineList.Count - 1; i >= 0; i--)
            {

                //再把绝对坐标转换成系统坐标
                //一个图例由四个点组成
                List<System.Drawing.PointF> PtList = new List<System.Drawing.PointF>();
                PointF pp1 = new PointF();
                pp1.X = f1.X;
                pp1.Y = f1.Y + (float)((this.ContourLineList.Count - i - 1) * stepY);
                PointF pp2 = new PointF((float)(pp1.X + this._legendWidth), (float)(pp1.Y));
                PointF pp3 = new PointF(pp2.X, (float)(pp1.Y + stepY));
                PointF pp4 = new PointF(pp1.X, (float)(pp1.Y + stepY));

                PtList.Add(pp1);
                PtList.Add(pp2);
                PtList.Add(pp3);
                PtList.Add(pp4);

                System.Drawing.SolidBrush brush = new System.Drawing.SolidBrush(Color.FromArgb((int)(255 * this.Opacity), this.ContourLineList[i].ContourLineFillColor));
                //画图例
                g.FillPolygon(brush, PtList.ToArray());
                //边框
                g.DrawPolygon(new Pen(Color.FromArgb((int)(255 * this.Opacity), Color.Black)), PtList.ToArray());
                //画字符串
                if (this._IsLegendTextFormat == true)  //启用图例文本格式化
                    g.DrawString(this.ContourLineList[i].ContourLineValue.ToString("E" + this._LegendFormatNum.ToString()), this._legendFont,
                        new System.Drawing.SolidBrush(Color.FromArgb((int)(255 * this.Opacity), this._legendColor)), pp3.X, pp3.Y - 10.0f);
                else
                    g.DrawString(this.ContourLineList[i].ContourLineValue.ToString("F"+this._LegendFormatNum.ToString()), this._legendFont,
                       new System.Drawing.SolidBrush(Color.FromArgb((int)(255 * this.Opacity), this._legendColor)), pp3.X, pp3.Y - 10.0f);

            }


        }

        # endregion


    }
}
